package com.nuanshui.heatedloan.task.proxy;

import java.lang.reflect.Field;
import java.lang.reflect.Method;

import com.nuanshui.heatedloan.task.util.JavassistCompiler;
/**
 * 动态生成消息监听器的工厂类
 * @param 
 * @author guohao
 * @date 2017年2月13日 上午9:56:20
 * @since $
 */
public class JavassistMessageListenerBeanClassFactory  extends AbstractMessageListenerBeanClassFactory  {
	
	public static String beanSource = "";
	
	private JavassistCompiler javassistCompiler = new  JavassistCompiler();
	
	static {
		
		StringBuffer sf = new StringBuffer();
		sf.append("package  com.nuanshui.heatedloan.task;").append("\n");
		sf.append("import org.springframework.util.MethodInvoker;\n");
		sf.append("import org.springframework.amqp.core.Message;\n");
		sf.append("import com.nuanshui.heatedloan.task.util.ExcutorTaskMsg;\n");
	    sf.append("import com.nuanshui.heatedloan.task.annotation.Task;\n");
		sf.append("import com.rabbitmq.client.Channel;\n");
		sf.append("public class ClassName { ").append("\n");
		sf.append("private  org.springframework.util.MethodInvoker methodInvoker=null;\n");
		sf.append("private  ExcutorTaskMsg excutorTaskMsg=null;\n");
		sf.append("private  Task task=null;\n");
		
		sf.append("public void setTask(Task task){ ");
		sf.append("     this.task = task; ");
		sf.append("} ").append("\n");
		
		sf.append("public void setExcutorTaskMsg(ExcutorTaskMsg excutorTaskMsg){ ");
		sf.append("     this.excutorTaskMsg = excutorTaskMsg; ");
		sf.append("} ").append("\n");
		
		sf.append("public void  setMethodInvoker(MethodInvoker methodInvoker){ ");
		sf.append("     this.methodInvoker = methodInvoker; ");
		sf.append("} ").append("\n");
		
		sf.append("public void onMessage(Message message, Channel channel){ ");
		sf.append("      excutorTaskMsg.onMessage(message,channel,methodInvoker,task);");
		sf.append("   } ").append("\n");
		sf.append("}").append("\n");
		beanSource = sf.toString();
	}
	
	@Override
	public MetaClass doCreateProxyClass(String className) {
		String code = beanSource.replace("ClassName", className);
		Class clazz =   javassistCompiler.compile(code, JavassistMessageListenerBeanClassFactory.class.getClassLoader());
        Method method =  parseOnMessageMethod(clazz);
        MetaClass metaClass = new MetaClass(clazz, method);
		return metaClass;
	}
	
	private static Method parseOnMessageMethod(Class clazz) {
		 Method methods[] =  clazz.getMethods();
		 for(Method method :methods) {
			 if(method.getName().equals("onMessage")) return method;
		 }
		
		 return null;
	}
	
	public static void main(String[] args) {
		JavassistMessageListenerBeanClassFactory factory = new JavassistMessageListenerBeanClassFactory();
		
		MetaClass  metaClass  =  factory.createProxyClass("Test0001");
		Class class1 = metaClass.getTargetClass();
		System.out.println(class1);
		Field fields[] = class1.getDeclaredFields();
		for(Field field :fields) {
		    System.out.println(field.getName());  
		}
		
		Method methods[]= class1.getDeclaredMethods();
		for(Method method :methods) {
			System.out.println(method.getName());
		}
	}
	
	

}
